package com.xbongbong.sys.model;


import com.alibaba.fastjson.JSONArray;
import com.xbongbong.paas.toolbox.exception.XbbException;
import com.xbongbong.paas.toolbox.wrap.IModel;
import com.xbongbong.sys.domain.entity.DepartmentEntity;
import com.xbongbong.sys.domain.entity.UserEntity;

import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.Set;

/**
 * @author kaka
 * @date  2018-9-4 16:50
 */
public interface DepartmentModel extends IModel<DepartmentEntity> {

    /**
     * 批量更新
     * @param departmentList
     * @param corpid
     * 创建时间 2020/12/14 3:24 PM
     * 修改时间 2020/12/14 3:24 PM
     * @author chy
     */
    void updateBatch(List<DepartmentEntity> departmentList, String corpid);

    /**
     * 批量更新部门id在idIn内的部门的del字段
     * @param del 批量将部门的del 字段设为 {del} 值
     * @param updateTime 更新时间
     * @param idIn 要更新的部门id集合
     * @param corpid 公司corpid
     */
    void batchUpdateDel(Integer del, Integer updateTime, List<Long> idIn, String corpid);

    /**
     * 批量更新部门id不在idIn内的部门的del字段
     * @param del 批量将部门的del 字段设为 {del} 值
     * @param updateTime 更新时间
     * @param idNotIn 不要更新的部门id集合，其他本公司的部门都要更新
     * @param corpid 公司corpid
     */
    void batchUpdateDelNotIn(Integer del, Integer updateTime, List<Long> idNotIn, String corpid);

    /**
     * 通过主键删除
     *
     * @param key    主键
     * @param corpid 公司id
     * @return Integer
     * @author GuoJun.HU
     * @date 2019/2/18 22:07
     * @since V1.0
     */
    Integer deleteByKey(String key, String corpid);

    /**
     * 根据部门 id 和公司corpid获取部门实体
     * @param departmentId 部门id
     * @param corpid 公司corpid
     * @return corpid 和 departmentId 对应的部门实体
     */
    DepartmentEntity getByKey( Long departmentId, String corpid);

    /**
     * 获取本公司所有的部门列表
     * @param corpid 公司id
     * @param showHidden 是否显示隐藏部门（即del = 2的部门），true 显示，false 不显示
     * @return 本公司所有部门/本公司所有可见部门
     * @throws XbbException
     */
    List<DepartmentEntity> findAllDepartment(String corpid, boolean showHidden) throws XbbException;

    /**
     * 获取自定义可选范围筛选后的部门列表
     * @param corpid 公司id
     * @param showHidden 是否显示隐藏部门（即del = 2的部门），true 显示，false 不显示
     * @param deptConditions 部门自定义可选范围
     * @return java.util.List<com.xbongbong.sys.domain.entity.DepartmentEntity>
     * @author sunshaoxiang
     * @Date  2020/09/23 19:24
     **/
    List<DepartmentEntity> findAllDepartment(String corpid, boolean showHidden,  Map<String, List<Long>> deptConditions);

    /**
     * 构建公司部门树
     * @param corpid 公司id
     * @param userList 用于构建部门 + 员工的树结构
     * @param type 类型，"department" 表示只需要部门结构，"staff" 表示需要部门 + 员工
     * @param showHidden 是否显示隐藏部门（即del = 2的部门），true 显示，false 不显示
     * @param simple 是否返回简单格式
     * @return 部门树
     * @throws XbbException 业务异常
     */
    JSONArray getDepartmentJsonTree(String corpid, List<UserEntity> userList, String type, boolean showHidden, boolean simple) throws XbbException;

    /**
     * 构建部门可选范围部门树
     * @param corpid 公司id
     * @param userList 用于构建部门 + 员工的树结构
     * @param type 类型，"department" 表示只需要部门结构，"staff" 表示需要部门 + 员工
     * @param showHidden 是否显示隐藏部门（即del = 2的部门），true 显示，false 不显示
     * @param simple 是否返回简单格式
     * @param deptConditions 部门可选范围条件
     * @return com.alibaba.fastjson.JSONArray
     * @author sunshaoxiang
     * @Date  2021/09/23 19:21
     * @throws XbbException 业务异常
     **/
    JSONArray getDepartmentJsonTree(String corpid, List<UserEntity> userList, String type, boolean showHidden, boolean simple, Map<String, List<Long>> deptConditions) throws XbbException;

    /**
     * 构建公司部门树
     * @param corpid 公司id
     * @param showHidden 是否显示隐藏部门（即del = 2的部门），true 显示，false 不显示
     * @return 部门树
     * @throws XbbException 业务异常
     */
    JSONArray getDepartmentJsonTree(String corpid, boolean showHidden) throws XbbException;

    /**
     * 构建部门树
     * @param corpid 公司id
     * @param showHidden 是否显示隐藏部门（即del = 2的部门），true 显示，false 不显示
     * @param departmentEntities 权限内的部门
     * @param simple 简单结构的部门树
     * @return 部门树
     * @throws XbbException 业务异常
     */
    JSONArray getSubDeptJsonTree(String corpid, boolean showHidden, List<DepartmentEntity> departmentEntities, Boolean simple) throws XbbException;


    /**
     * 构建部门树
     * @param corpid 公司id
     * @param showHidden 是否显示隐藏部门（即del = 2的部门），true 显示，false 不显示
     * @param departmentEntities 权限内的部门
     * @param simple 简单结构的部门树
     * @param selectDepartmentList 选择的部门
     * @return 部门树
     * @throws XbbException 业务异常
     */
    JSONArray getSubDeptJsonTreeByDeptId(String corpid, boolean showHidden, List<DepartmentEntity> departmentEntities, Boolean simple, List<DepartmentEntity> selectDepartmentList) throws XbbException;

    /**
     * 构建公司部门树，简单格式
     * @param corpid 公司id
     * @param showHidden 是否显示隐藏部门（即del = 2的部门），true 显示，false 不显示
     * @return 部门树,简单格式
     * @throws XbbException 业务异常
     */
    JSONArray getDepartmentSimpleJsonTree(String corpid, boolean showHidden) throws XbbException;


    /**
     * 构建自定义部门范围的平铺部门树
     * @param corpid 公司id
     * @param showHidden 是否显示隐藏部门（即del = 2的部门），true 显示，false 不显示
     * @param deptConditions 自定义部门范围
     * @return com.alibaba.fastjson.JSONArray
     * @author sunshaoxiang
     * @Date  2021/09/23 19:19
     * @throws XbbException 业务异常
     **/
    JSONArray getDepartmentSimpleJsonTree(String corpid, boolean showHidden, Map<String, List<Long>> deptConditions) throws XbbException;

    /**
     * 通过 depIdIn 集合获取部门列表
     * @param corpid 公司id
     * @param depIdIn 部门id集合
     * @return 集合获取部门列表
     */
    List<DepartmentEntity> getByDepIdIn(String corpid, Collection<Long> depIdIn);

    /**
     * 获取符合条件的部门id列表
     * @param param 检索条件
     * @return 符合条件的部门id列表
     */
    List<Long> getDepIds(Map<String, Object> param);

    /**
     * 根据部门id获取部门列表
     * @param departmentIds 部门id列表
     * @param corpid 公司id
     * @return 符合部门id的列表
     */
    List<DepartmentEntity> findEntitysByDepartmentIds(List<Long> departmentIds, String corpid);

    /**
     * 获取部门的下面的所有子部门的部门id列表,不考虑隐藏部门
     * @param corpid 公司corpid
     * @param depIdIn 要获取子部门ids的所有部门ids
     * @return depIdIn 及其递归子部门的部门id列表
     */
    List<Long> getSubDepIdList(String corpid, Collection<Long> depIdIn);

    /**
     * 获取部门的下面的所有子部门的部门id列表
     * @param corpid 公司corpid
     * @param depIdIn 要获取子部门ids的所有部门ids
     * @param showHidden 是否考虑隐藏部门（即del = 2的部门），true 显示，false 不显示
     * @return depIdIn 及其递归子部门的部门id列表
     */
    List<Long> getSubDepIdList(String corpid, Collection<Long> depIdIn, boolean showHidden);

    /**
     * 获取某个部门下一个层级的部门（即父部门为选择的部门）
     * @param corpid 公司id
     * @param depId 部门id
     * @return
     * @throws
     *
     * @author hongxiao
     * @date: 2019-02-19 14:52
     * @since v1.0
     * @version v1.0
     */
    List<DepartmentEntity> getSubOneLevel(String corpid, Long depId);
    /**
     *
     * @param corpid
     * @param depId
     * @param containSup 是否包含父部门本身
     * @return java.util.List<com.xbongbong.sys.domain.entity.DepartmentEntity>
     * @throws
     * @author zcp
     * @since v1.0
     * @version v1.0
     */
    List<DepartmentEntity> getSubOneLevel(String corpid, Long depId, boolean containSup);
    /**
     * 从缓存获取部门下一级的子部门
     * @param corpid
     * @param depId
     * @param containSup 是否包含父部门本身
     * @return java.util.List<com.xbongbong.sys.domain.entity.DepartmentEntity>
     * @author zcp
     * @since v1.0
     * @version v1.0
     */
    List<DepartmentEntity> getSubOneLevelFromJedis(String corpid, Long depId, boolean containSup);

    /**
     * 获取部门的下面的所有子部门
     *
     * @param corpid 公司id
     * @param depIdIn 要获取子部门ids的所有部门ids
     * @param showHidden 是否考虑隐藏部门（即del = 2的部门），true 显示，false 不显示
     * @return 返回depIdIn的所有的子部门（包含本身）
     * @since performance-v1.0
     * @version performance-v1.0
     * @author chuanpeng.zhang
     * @author kaka
     * 创建时间：2018年11月2日 下午4:08:55
     * 修改时间：2018-11-5 by zcp 参数depIdIn由list类型改为set类型（因缓存方案要用到hashCode，list的hashCode对内部的顺序有严格限制）
     */
    List<DepartmentEntity> getSubDepList(String corpid, Collection<Long> depIdIn, boolean showHidden);

    /**
     * 从缓存获取部门的子部门
     * 参数depIdIn由list类型改为set类型（因缓存方案要用到hashCode，list的hashCode对内部的顺序有严格限制）
     *
     * @param corpid  公司id
     * @param depIdIn 部门ids
     * @return
     * @throws
     * @author hongxiao
     * @date: 2019-01-31 16:30
     * @version v1.0
     * @since v1.0
     * @update by zcp 从main-service移入 2019-03-27
     */
    List<DepartmentEntity> getSubDepListFromJedis(String corpid, Set<Long> depIdIn);


    /**
     * 清理空部门，设置del=2
     * @param corpid 公司id
     */
    void clearEmptyDepartment(String corpid);

    /**
     * 更新整个公司的del字段为${conditionDel}的数据值为${del}
     * @param del 需要设置为del为该值
     * @param updateTime 更新时间
     * @param conditionDel del筛选条件
     * @param corpid 公司id
     */
    void batchUpdateDelByDel(Integer del, Integer updateTime, Integer conditionDel, String corpid);

    /**
     * 获取部门的Map  部门id：部门实体，数据准备，不用多次差库
     * @param corpid 公司id
     * @param depIdIn 部门id集合，=null时查全公司
     * @return 部门id与部门实体为键值对的Map
     */
    Map<Long, DepartmentEntity> getDeptsMap(String corpid, List<Long> depIdIn);


    /**
     * 根据router正则表达式获取相应的departmentId列表
     * @param corpid
     * @param routerRegexp
     * @return
     * @author kaka
     * @time 2016年8月26日 下午7:04:10
     */
    List<Long> getDepartmentIdsByRegexp(String corpid, String routerRegexp);

    /**
     * 批量删除部门，根据部门ID列表和公司ID
     * @param keys 部门id列表
     * @param corpid 公司id
     * @return 影响记录数
     */
    Integer deleteByKeys(List<Long> keys, String corpid);

    /**
     * 通过公司ID和部门ID获取部门实体，不管del为1还是0
     * @param key 部门id
     * @param corpid 公司id
     * @return 返回对应的部门实体，若找不到则返回null
     */
    DepartmentEntity getByKeyIgnoreDel(String key, String corpid);

    /**
     * 处理业绩目标内的员工所在部门名
     *
     * @param corpid   公司id
     * @param userList 员工列表
     * @return userId--员工所在部门名称合集
     * @author hongxiao
     * @date: 2019-02-21 14:32
     * @version v1.0
     * @since v1.0
     * @update 2019-4-1 从main-service移入 by zcp
     */
    Map<String, String> formatUserDepNames(String corpid, List<UserEntity> userList);

    /**
     * 根据部门ID集合获取部门名称
     *
     * @param corpId 公司id
     * @param depIdIn 部门列表
     * @param ignoreDel 是否忽略del=0的条件
     * @return 部门实体
     */
    List<DepartmentEntity> getDepartmentNamesByIds(String corpId, Collection<Long> depIdIn, boolean ignoreDel);

    /**
     * 通过名称获取部门
     *
     * @param names     部门名称，"-"分割
     * @param corpid    公司id
     * @author GuoJun.HU
     * @since V1.0
     * @return Map
     * @date 2019/5/21 16:21
     */
    Map<String, Object> getDepIdByNames(String names, String corpid);

    /**
     * Description: 获取部门的上面的所有父部门的部门id列表
     * @param corpid 公司corpid
     * @param depIds 要获取子部门ids的所有部门ids
     * @param showHidden 是否考虑隐藏部门（即del = 2的部门），true 显示，false 不显示
     * @return java.util.List<java.lang.Long>
     * @author 魏荣杰
     * @date 2019/9/5 17:02
     * @since v4.3.1
     */
    List<Long> getSupDepIdList(String corpid, Collection<Long> depIds, boolean showHidden);

    /**
     * 获取所有部门对应的下属部门ID
     * @param corpid 公司ID
     * @param showHidden 是否考虑隐藏部门（即del = 2的部门），true 显示，false 不显示
     * @return java.util.Map
     * @author zhouwq
     * @date 2020/9/4 10:24
     */
    Map<Long, List<Long>> getSubDepIdMap(String corpid, boolean showHidden);
}